Skip to content

Support for cross-compiling on Linux#465

Draft
universeindex wants to merge 43 commits intosmartcmd:mainfrom
universeindex:main
Draft

Support for cross-compiling on Linux#465
universeindex wants to merge 43 commits intosmartcmd:mainfrom
universeindex:main

Conversation

@universeindex
Copy link

Description

I've implemented support for cross-compiling a Windows build on a Linux host using clang-cl. I added a toolchain file at cmake/LinuxCrosscompile.cmake that achieves this. I also modified many source files to not use backslashes in include statements (which error with clang-cl) and use case-sensitive paths (many Linux filesystems are case-sensitive, unlike NTFS, which causes errors). I avoided changing actual functionality as much as possible, so I hope this isn't too intrusive. Additionally I apologize for the messy commit messages, I hope this isn't a big issue, I have detailed all of the changes I made here.

Changes

Include statements use forward slashes instead of backslashes
Include statements reference files with correct capitalization
Added a CMake toolchain file for using clang-cl on Linux
Minecraft.Client/Xbox/MinecraftWindows.rc is not compiled on Linux, this causes errors otherwise, as it can't find the windows SDK and I am unsure how to specify the location here.
I also added documentation for building on Linux.

Previous Behavior

Running CMake on Linux would throw a hardcoded error stating that Linux isn't supported. When removed, and clang-cl is set to be used, many errors occur due to include paths using backslashes and inconsistent capitalization. The only way to build and run on Linux before is to use a Windows VM, and there is no way to get proper code completion on a Linux IDE.

Root Cause

Backslashes in include paths are supported on Windows, but not other systems, and NTFS is case-insensitive, so include paths do not have to match capitalization, also not on other systems.

New Behavior

The game now compiles and outputs a Windows binary on Linux using clang-cl.

Fix Implementation

See changes section

@universeindex
Copy link
Author

P.S. I tested building on Windows, which still works fine, so hopefully there shouldn't be any issues

@universeindex
Copy link
Author

Most commits made to upstream will probably conflict with those by overwriting the includes I changed back with backslashes, but I'll be fixing those until this is merged

@universeindex
Copy link
Author

universeindex commented Mar 4, 2026

I tested CMake w/ visual studio generator on Windows (with MSVC) which worked fine, but I haven't tried the normal .sln yet. I can do that now, but it might be a minute, i'm working on a really slow machine currently

@universeindex
Copy link
Author

works fine, compiles and runs w/ visual studio build ^

@universeindex
Copy link
Author

I did rewrite Minecraft.Client/iob_shim.asm in C++ as IobShim.cpp because I couldn't get MASM to work under Linux, but that's it aside from the includes I believe.

@DwifteJB
Copy link

DwifteJB commented Mar 4, 2026

can confirm does compile on linux w/ cmake

well done :)

set(CMAKE_C_COMPILER_FRONTEND_VARIANT MSVC)
set(CMAKE_CXX_COMPILER_FRONTEND_VARIANT MSVC)

add_compile_options(/winsysroot /opt/msvc --target=x86_64-pc-windows-msvc -fms-compatibility -fms-extensions -fdelayed-template-parsing)
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the cmake file assumes /opt/msvc whereas https://github.com/mstorsjo/msvc-wine recommends ~/my_msvc/opt/msvc

just a simple issue as you can syslink or run the msvc-wine installer as root & install to /opt/msvc

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

oh, good catch, i think i might set it to CMAKE_BINARY_DIR/msvc so users can symlink one instead, or if theres a way to set options of a toolchain file that would be best
will change soon, not home atm

Copy link

@DwifteJB DwifteJB Mar 4, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

msvc-wine sets itself in the path directory (although the user has to set this up manually through something like .zshrc)

could do something like

whereis msbuild

to determine the directory?

if it isn't set as CMAKE_MSVC_DIR

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

opened pr on your fork that fixes this & a clang error universeindex#1

@DwifteJB
Copy link

DwifteJB commented Mar 4, 2026

I think __iob_func should be implemented as __declspec(naked) + __asm.

_declspec(naked) seems to not be working since __asm seems to have been dropped for x64 (if you want to use it you have to use a .asm file, like how 4J seems to have done it)

__attribute__((naked)) & __asm__() works however

@DwifteJB
Copy link

DwifteJB commented Mar 4, 2026

will need someone to test compiling on windows however

@DRAGONTOS
Copy link

i dont seem to be able to compile this
image

@DwifteJB
Copy link

DwifteJB commented Mar 4, 2026

I think __iob_func should be implemented as __declspec(naked) + __asm.

_declspec(naked) seems to not be working since __asm seems to have been dropped for x64 (if you want to use it you have to use a .asm file, like how 4J seems to have done it)
__attribute__((naked)) & __asm__() works however

Forgot about it that, as I am used to x86 development. Uncool, Microsoft. Anyway, maybe conditionally use the .asm file for MSVC assembler and .cpp with [[__gnu__::__naked__]] for Clang-cl?

yeah i havent done much c++ for a good few years and thought it still existed,

this seems to work though https://github.com/DwifteJB/MinecraftConsoles/blob/ee78a74025b78b0c5c813a7beb7c94629a30c2ff/Minecraft.Client/IobShim.cpp

@DRAGONTOS
Copy link

i got msvc-wine installed do

@DwifteJB
Copy link

DwifteJB commented Mar 4, 2026

i dont seem to be able to compile this image

seems to be an issue with msvc, try this fork/pr https://github.com/DwifteJB/MinecraftConsoles/tree/msvc-winsysroot-fix might just fix it (with branch msvc-winsysroot-fix)

@DwifteJB
Copy link

DwifteJB commented Mar 4, 2026

this seems to work though https://github.com/DwifteJB/MinecraftConsoles/blob/ee78a74025b78b0c5c813a7beb7c94629a30c2ff/Minecraft.Client/IobShim.cpp

Good attempt, but there is a unified asm syntax for both AT&T and Intel in the same code without preprocessor mess. Both clang and GCC support it so please look into it, I forgot how exactly that works but search for it.

something like:

extern "C" FILE* __cdecl __acrt_iob_func(unsigned index);

extern "C" __attribute__((naked)) FILE* __cdecl __iob_func(void) {
    __asm__(
        ".intel_syntax noprefix\n\t"
        "xor ecx, ecx\n\t"
        "jmp __acrt_iob_func\n\t"
        ".att_syntax prefix"
    );
}

grabbed from: https://cboard.cprogramming.com/windows-programming/138371-intel-assembly-syntax-gcc.html

@DwifteJB
Copy link

DwifteJB commented Mar 4, 2026

No, I didn't mean that one, but .intel_syntax may be a solution(?)

seems to be compiling (at the very least) & seems to be almost identical other than the clang unreachable trap

@Twig6943
Copy link
Contributor

@Twig6943 is it this workflow file?

DwifteJB@1825f46

also, can confirm builds on vs 2022 image

yes its that one, Here's a run showcasing it being stuck on the end https://github.com/Twig6943/MinecraftConsoles/actions/runs/22801883533/job/66144749796

@xgui4
Copy link

xgui4 commented Mar 12, 2026

i do not care if it work with visual studio i want to compile it via my gnu/linux machine without microslop winslop vm

???? you been able to do that since last week-ish???

how ?

@Twig6943
Copy link
Contributor

i do not care if it work with visual studio i want to compile it via my gnu/linux machine without microslop winslop vm

???? you been able to do that since last week-ish???

how ?

Clone the repo of this pr;

Do this
image
and itll build

@Twig6943
Copy link
Contributor

Run seems to be stuck https://github.com/DwifteJB/MinecraftConsoles/actions/runs/23008712897/job/66812791427

1294/1296

It builds fine on a local machine but gets stuck on github actions, idk what's up with that. You can just seperate the actions stuff into its own pr as discussed above.

Thanks for getting the ball rolling on this btw

@DwifteJB
Copy link

seems like it, ill check to see whats going on with it now by running the actions locally

@Twig6943
Copy link
Contributor

seems like it, ill check to see whats going on with it now by running the actions locally

I meant like just running the commands manually, idk if it'll get stuck or not when using a self hosted runner

#465 (comment)

@DwifteJB
Copy link

seems like it, ill check to see whats going on with it now by running the actions locally

I meant like just running the commands manually, idk if it'll get stuck or not when using a self hosted runner

#465 (comment)

testing with act via a docker compose file (just to see if it runs), might be due to it being in a container, being stuck after stubs is super confusing, so im just making it run on ubuntu itself rather than an arch linux container within it...

@Twig6943
Copy link
Contributor

so im just making it run on ubuntu itself rather than an arch linux container within it...

Could be the case ig? I tried fedora and it also got stuck at the same place

@DwifteJB
Copy link

so im just making it run on ubuntu itself rather than an arch linux container within it...

Could be the case ig? I tried fedora and it also got stuck at the same place

seems to be the only thing that makes sense, may be missing a dependency but i would've thought itd error out

@universeindex
Copy link
Author

hi sorry for the inactivity, I'll get on helping fix this up later today

@DwifteJB
Copy link

hi sorry for the inactivity, I'll get on helping fix this up later today

hi! if you read up builds are basically working, fixing build-linux.yml now

@DwifteJB
Copy link

testing now, not sure if its due to some issue with wine display or via a race condition occuring & causing a file to be locked... will see

@Twig6943
Copy link
Contributor

testing now, not sure if its due to some issue with wine display or via a race condition occuring & causing a file to be locked... will see

You're still using arch which defeats the whole purpose?

image

@DwifteJB
Copy link

DwifteJB commented Mar 12, 2026

testing now, not sure if its due to some issue with wine display or via a race condition occuring & causing a file to be locked... will see

You're still using arch which defeats the whole purpose?
image

too many issues with ubuntu & clang, no clue why. even though they ARE installed??? https://github.com/DwifteJB/MinecraftConsoles/actions/workflows/build-linux.yml

@Twig6943
Copy link
Contributor

@DwifteJB I'm not sure where you got the assumption that it being stuck is related to not having a display

image

This builds fine which doesn't have a display;

https://github.com/nocss42/GardenGate/blob/dedicated/.github/workflows/dll_linux.yml
https://github.com/nocss42/GardenGate/actions/runs/22844455449

@DwifteJB
Copy link

@DwifteJB I'm not sure where you got the assumption that it being stuck is related to not having a display
image

This builds fine which doesn't have a display;

https://github.com/nocss42/GardenGate/blob/dedicated/.github/workflows/dll_linux.yml https://github.com/nocss42/GardenGate/actions/runs/22844455449

assumption since it got stuck on my local machine when i didnt have a display connected

@Twig6943
Copy link
Contributor

Twig6943 commented Mar 12, 2026

I don't know why it requires a display for this to be built but not gardengate anyways could you convert it to wlheadless-run with cage? (That is once it builds w xvfb lol)

for arch it'd be

sudo pacman -S cage
yay -S xwayland-run # I'm working on getting this package into the official repos
wlheadless-run -c cage -- commandyouwannarunhere

Edit: yea nevermind it seems to be stuck at 1104 with xvfb so won't make a difference

@DwifteJB
Copy link

I don't know why it requires a display for this to be built but not gardengate anyways could you convert it to wlheadless-run with cage? (That is once it builds w xvfb lol)

for arch it'd be

sudo pacman -S cage
yay -S xwayland-run # I'm working on getting this package into the official repos
wlheadless-run -c cage -- commandyouwannarunhere

Edit: yea nevermind it seems to be stuck at 1104 with xvfb so won't make a difference

atp lets ignore the actions file & sort it out in a different pr

@Twig6943
Copy link
Contributor

Twig6943 commented Mar 12, 2026

I don't know why it requires a display for this to be built but not gardengate anyways could you convert it to wlheadless-run with cage? (That is once it builds w xvfb lol)
for arch it'd be

sudo pacman -S cage
yay -S xwayland-run # I'm working on getting this package into the official repos
wlheadless-run -c cage -- commandyouwannarunhere

Edit: yea nevermind it seems to be stuck at 1104 with xvfb so won't make a difference

atp lets ignore the actions file & sort it out in a different pr

Yea as I said it should be looked into later

Shoot that pr and will prob be merged soon

@DwifteJB
Copy link

@universeindex universeindex#4 very simple fix inside

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.